﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using VTV.TaskManagementSystem.Entities;

namespace VTV.TaskManagementSystem.DataAccess
{
    public partial class TaskTeam : IConvertToLinqEntity<TaskTeam>, ISetting<Entities.TaskTeam>
    {
        public string ErrorMessage { get; set; }

        public TaskTeam Convert(object baseEntity)
        {
            TaskTeam result = null;
            try
            {
                if (baseEntity != null)
                {
                    var entity = (Entities.TaskTeam)baseEntity;

                    return result = new TaskTeam
                    {
                        TaskID = entity.TaskID,
                        ActualEndDate = entity.ActualEndDate,
                        ExpectedEndDate = entity.ExpectedEndDate,
                        StartDate = entity.StartDate,
                        Status = entity.Status,
                        Comments = String.IsNullOrEmpty(entity.Comments) ? string.Empty : entity.Comments,
                        TeamID = entity.TeamID
                    };
                }
                else
                {
                    ErrorMessage = Common.Constant.ErrorMessage.SOURCE_IS_NULL;
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;
            }

            return result;
        }

        public bool AddNew(Entities.TaskTeam source)
        {
            try
            {
                var newSource = this.Convert(source);

                using (var data = new DataBaseDataContext())
                {
                    data.TaskTeams.InsertOnSubmit(newSource);
                    data.SubmitChanges();
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return false;
            }

            return true;
        }

        public bool Delete(Entities.TaskTeam source)
        {
            try
            {

                using (var data = new DataBaseDataContext())
                {
                    var newSource = data.TaskTeams.FirstOrDefault(p => p.TaskTeamID == source.TaskTeamID);
                    if (newSource == null) return false;

                    data.TaskTeams.DeleteOnSubmit(newSource);
                    data.SubmitChanges();

                    return true;
                }

            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return false;
            }
        }

        public bool Update(Entities.TaskTeam source)
        {
            try
            {
                using (var data = new DataBaseDataContext())
                {
                    var employee = data.TaskTeams.FirstOrDefault(p => p.TaskTeamID == source.TaskTeamID);
                    if (employee != null)
                    {
                        employee.Comments = String.IsNullOrEmpty(source.Comments) ? null : source.Comments;
                        employee.ExpectedEndDate = source.ExpectedEndDate;
                        employee.Status = source.Status;
                        employee.StartDate = source.StartDate; ;

                        data.SubmitChanges();

                        return true;
                    }
                    else
                    {
                        ErrorMessage = Common.Constant.SqlErrorMessage.NOT_EXIST_OBJECT_IN_DB;

                        return false;
                    }
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return false;
            }
        }

        public Entities.TaskTeam GetTaskTeam(int taskTeamID)
        {
            try
            {
                using (var data = new DataBaseDataContext())
                {
                    var result = (from p in data.TaskTeams
                                  where p.TaskTeamID == taskTeamID
                                  select new Entities.TaskTeam
                                  {
                                      TeamID = p.TeamID,
                                      ExpectedEndDate = p.ExpectedEndDate,
                                      TaskID = p.TaskID,
                                      StartDate = p.StartDate,
                                      ActualEndDate = p.ActualEndDate,
                                      Comments = p.Comments,
                                      Status = p.Status
                                  }).FirstOrDefault();

                    return result;
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return null;
            }
        }

        public IEnumerable<Entities.TaskTeamShow> GetTaskTeamShow(int taskID)
        {
            try
            {
                using (var data = new DataBaseDataContext())
                {
                    var a = (from p in data.TaskTeams
                             where p.TaskID == taskID
                             select p).ToList();

                    var result = (from p in data.TaskTeams.AsEnumerable()
                                  where p.TaskID == taskID
                                  select new Entities.TaskTeamShow()
                                  {
                                      ActualEndDate = p.ActualEndDate,
                                      TeamID = p.TeamID,
                                      TaskID = p.TaskID,
                                      TaskTeamID = p.TaskTeamID,
                                      ExpectedEndDate = p.ExpectedEndDate,
                                      StartDate = p.StartDate,
                                      Status = p.Status,
                                      Comment = (String.IsNullOrEmpty(p.Comments) ? String.Empty : p.Comments),
                                      TeamName = (String.IsNullOrEmpty(p.Team.Name) ? String.Empty : p.Team.Name)
                                  }).ToList();

                    return result;
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return null;
            }
        }

        public IEnumerable<Entities.ShowMe> GetDefaultToShow(DateTime? currentDate, string teamName, DateTime? startDate, DateTime? endDate)
        {
            try
            {
                using (var data = new DataBaseDataContext())
                {
                    var baseData = teamName != null && teamName.Equals("all") ?
                                    data.sp_GetDefaultObjectToShow(null, null, null, null).ToList() :
                                        teamName != null && teamName.ToLower().Equals("week") ?
                                        data.sp_GetDefaultObjectToShow(currentDate, null, null, null).ToList() :
                                        data.sp_GetDefaultObjectToShow(currentDate, startDate, endDate, teamName).ToList();

                    var result = new List<ShowMe>();

                    var taskBase = baseData.GroupBy(p => p.TaskTeamID).ToList();

                    taskBase
                        .ForEach(taskteam => taskteam
                        .GroupBy(v => v.TaskID)
                        .ToList()
                        .ForEach(results =>
                                         {
                                             var taskObj = new ShowMe()
                                                           {
                                                               TaskID = results.First().TaskID,
                                                               TaskName = results.First().TaskName,
                                                               TaskDescription = results.First().Descritions
                                                           };
                                             var teamList = new List<TeamToShow>();
                                             results.GroupBy(z => z.TeamID).ToList()
                                                    .ForEach(team =>
                                                                {
                                                                    if (team.First().TeamID.HasValue)
                                                                    {
                                                                        teamList.Add(new TeamToShow()
                                                                        {
                                                                            TeamID = team.First().TeamID,
                                                                            ExpectedEndDate = team.First().ExpectedEndDate,
                                                                            StartDate = team.First().StartDate,
                                                                            Status = team.First().Status,
                                                                            Comment = team.First().Comments,
                                                                            TeamName = team.First().Name
                                                                        });

                                                                        var employeeList = new List<EmployeeToShow>();
                                                                        team.ToList()
                                                                            .ForEach(emp =>
                                                                                         {
                                                                                             if (emp.EmployeeID.HasValue)
                                                                                             {
                                                                                                 employeeList.Add(new EmployeeToShow()
                                                                                                 {
                                                                                                     EmployeeID = emp.EmployeeID,
                                                                                                     IsTeamLead = emp.IsTeamLead,
                                                                                                     EmployeeName = emp.FullName
                                                                                                 });
                                                                                             }
                                                                                         });
                                                                        teamList.Last().EmployeeToShows = employeeList;
                                                                    }
                                                                });
                                             taskObj.TeamToShows = teamList;
                                             result.Add(taskObj);
                                         }));

                    return result;
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return null;
            }
        }

        public IEnumerable<Entities.ShowMeVer2> GetDefaultToShowVer2(DateTime? currentDate, string teamName, DateTime? startDate, DateTime? endDate)
        {
            try
            {
                using (var data = new DataBaseDataContext())
                {
                    var baseData = teamName != null && teamName.ToLower().Equals("all") ?
                                    data.sp_GetDefaultObjectToShow(null, null, null, null).ToList() :
                                        teamName != null && teamName.ToLower().Equals("week") ?
                                        data.sp_GetDefaultObjectToShow(currentDate, null, null, null).ToList() :
                                        data.sp_GetDefaultObjectToShow(currentDate, startDate, endDate, teamName).ToList();

                    var result = new List<ShowMeVer2>();

                    baseData.GroupBy(p => p.TaskTeamID)
                        .ToList()
                        .ForEach(taskteam => taskteam.GroupBy(v => v.TaskID).ToList()
                        .ForEach(task => task.GroupBy(t => t.TeamID)
                        .ToList()
                        .ForEach(team =>
                                     {

                                         var showMeVer2 = new ShowMeVer2()
                                         {
                                             TeamID = team.First().TeamID,
                                             TaskID = team.First().TaskID,
                                             TaskName = team.First().TaskName,
                                             ExpectedEndDate = team.First().ExpectedEndDate,
                                             StartDate = team.First().StartDate,
                                             Status = team.First().Status,
                                             TaskDescription = team.First().Descritions,
                                             TeamName = team.First().Name,
                                             Comments = team.First().Comments
                                         };

                                         if (team.First().EmployeeID.HasValue)
                                         {
                                             showMeVer2.EmployeeToShows = new List<EmployeeToShow>();

                                             team.ToList()
                                             .ForEach(employee => showMeVer2.EmployeeToShows.Add(new EmployeeToShow()
                                             {
                                                 EmployeeID = employee.EmployeeID,
                                                 EmployeeName = employee.FullName,
                                                 IsTeamLead = employee.IsTeamLead
                                             }));
                                         }

                                         result.Add(showMeVer2);
                                     })));


                    return result;
                }
            }
            catch (Exception e)
            {
                ErrorMessage = e.Message;

                return null;
            }
        }
    }
}
